from rest_framework import serializers
from .models import Order, OrderDetail
from datetime import datetime
import random
from django_redis import get_redis_connection
from course.models import Course
from django.db import transaction

import logging

log = logging.getLogger("django")


class OrderModelSerializer(serializers.ModelSerializer):
    """订单序列化器"""

    # coupon = CouponSerializer()
    class Meta:
        model = Order
        fields = [
            "id", "order_title", "total_price",
            "real_price", "order_number", "order_status",
            "pay_type", "pay_time",
        ]
        extra_kwargs = {
            "id": {"read_only": True, },
            "order_title": {"read_only": True, },
            "total_price": {"read_only": True, },
            "real_price": {"read_only": True, },
            "order_number": {"read_only": True, },
            "order_status": {"read_only": True, },
            "pay_time": {"read_only": True, },
            "pay_type": {"required": True, },
        }

    def create(self, validated_data):
        """
        生成订单
        :param validated_data:
        :return:
        """
        # 接受客户端提交的数据
        pay_type = validated_data.get("pay_type")

        # 生成必要参数
        user_id = self.context["request"].user.id  # 在序列化器中获取视图中的数据，通过self.context
        # user_id = 1  # todo 回头我们学习怎么在序列化器中获取视图中的数据
        order_title = "购买"
        order_number = datetime.now().strftime("%Y%m%d%H%M%S") + ("%06d" % user_id) + ("%04d" % random.randint(0, 9999))
        order_status = 0

        # 从redis中提取勾选商品
        redis = get_redis_connection("cart")
        # 从购物车中一区订单信息
        course_set = redis.smembers("selected_%s" % user_id)

        # 如果没有任何勾选的商品，则不能继续下单
        if len(course_set) < 1:
            raise serializers.ValidationError("对不起，当前没有选中任何课程！")
        # 生成订单记录
        # order = super().create(**{
        #     "order_title": order_title,
        #     # 等后面生成订单详情的时候，需要循环购物车中商品时，再计算总价格，再填进来
        #     "total_price": 0,
        #     "real_price": 0,
        #     "order_number": order_number,
        #     "order_status": order_status,
        #     "pay_type": pay_type,
        #     "order_desc": "测试订单",
        #     "user_id": user_id,
        # })
        order = Order.objects.create(order_title=order_title, total_price=0,
                                     real_price=0, order_number=order_number,
                                     order_status=order_status, pay_type=pay_type,
                                     order_desc='测试订单', user_id=user_id)

        try:
            # 连接redis
            redis = get_redis_connection("cart")

            # 从购物车中一区订单信息
            course_set = redis.smembers("selected_%s" % user_id)
            cart_list = redis.hgetall("cart_%s" % user_id)
        except:
            log.error("redis存储出错！")
            return serializers.ValidationError("生成订单失败！请联系客服工作人员")

        # 声明订单总价格和订单实价
        total_price = 0

        for course_id_bytes in course_set:
            course_id = int(course_id_bytes.decode())
            try:
                course = Course.objects.get(pk=course_id)
            except:
                return serializers.ValidationError("对不起，商品课程不存在！")

            price = course.price

            # 生成订单详情记录
            order_detail = OrderDetail.objects.create(
                order=order,
                course=course,
                price=price,
                real_price=price
            )

            # 记录订单总价
            total_price += order_detail.price

        """3. 清除掉购物车中勾选的商品"""
        pip = redis.pipeline()
        pip.multi()
        for course_id_bytes in cart_list:
            if course_id_bytes in course_set:
                pip.hdel("cart_%s" % user_id, course_id_bytes)
                pip.srem("selected_%s" % user_id, course_id_bytes)
        pip.execute()

        order.total_price = total_price
        order.real_price = total_price  # 先默认当前商品总价是实付金额
        order.save()

        # 返回相应给客户端的订单模型
        return order

